package cn.chainco.cts.action;

import java.io.IOException;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.struts2.ServletActionContext;
import org.apache.struts2.convention.annotation.Action;
import org.apache.struts2.convention.annotation.InterceptorRef;
import org.dom4j.Document;
import org.dom4j.DocumentHelper;
import org.dom4j.Element;

import cn.chainco.cts.iservice.CommonManager;
import cn.chainco.cts.iservice.IPointManager;
import cn.chainco.cts.jdo.Country;
import cn.chainco.cts.jdo.Point;
import cn.chainco.cts.jdo.PointGroup;
import cn.chainco.cts.utils.CommUtils;
import cn.chainco.cts.utils.query.OP;
import cn.chainco.cts.utils.query.Page;
import cn.chainco.cts.utils.query.QueryOrder;
import cn.chainco.cts.utils.query.QueryParam;

import com.opensymphony.xwork2.ActionSupport;

@SuppressWarnings("unchecked")
@InterceptorRef("ctsInterceptors")
public class PointAction extends ActionSupport {
	private static final long serialVersionUID = 1L;

	private CommonManager commonManager;
	private IPointManager pointManager;

	private long id;	
	private int pageSize = 15;
	private int pageNumber = 1;
	@SuppressWarnings("rawtypes")
	private Page pager;
	private List<Point> pointList;
	private Point point;
	private List<Country> countryList;
	private Country country;
	private String keyword;
	private int portType = 0;
	private int moduleFlag;
	private PointGroup pointGroup;
	private List<PointGroup> pointGroupList;
	private String commonGroupName;
	
	private String pid;
	private String latlngs;
	private String detail;
	private String first;
	private int zoom;

	// 查询用
	private int type;
	private String pointName;
	private String pointGroupName;
	private String countryName;
	private int basePort;
	private String airCode;
	private int positionFlag;//已定位和未定位的标记

	// 此方法只执行一次
	public void onlyOne() {
		System.out.println("start");
		try {
			// pointManager.clearUpPoint();
		} catch (RuntimeException e) {
			e.printStackTrace();
		}
		System.out.println("end");
	}
	/**
	 * 其他网站过来获取地点
	 */
	private List<Point> getPointsByWWW(String pointsIds){
		List<Point> listPointIds = new ArrayList<Point>();
		if( !pointsIds.equals("all")){
			String ids[] = pointsIds.split(",");
			for( String obj:ids ){
				if( CommUtils.isCorrectInt(obj)){
					 Point point = this.commonManager.findEntityByPK(Point.class, Long.parseLong(obj) );
					 listPointIds.add( point );
				}
			}
			return listPointIds;
		}else{
			return null;
		}
	}
	/**
	 * 匹配名字
	 */
	private List<Point> matchName( List<Point> points,String keyword ){
		List<Point> list = new ArrayList<Point>();
		for( Point obj: points ){
			if( obj.getFullnameNoSymbol().toLowerCase().contains( keyword.toLowerCase())){
				list.add( obj );
			}
		}
		return list;
	}
	/**
	 * 匹配WWW的周边港口
	 */
	private List<Point> matchWWW( List<Point> list1,List<Point> list2 ){
		List<Point> list = new ArrayList<Point>();
		Set<Point> set = new HashSet<Point>();
		for( Point obj: list1 ){
			for( Point obj2: list2 ){
				if( obj.getId() == obj2.getId() ){
					set.add( obj2 );
				}
			}
		}
		for( Point obj: set ){
			list.add( obj );
		}
		return list;
	}
	/**
	 * 模糊查询Point 传值portType：0查海港+内陆；1查海港；2查空港+内陆；3查空港；4内陆
	 */
	@Action("searchPointBykeyword")
	public String searchPointBykeyword() {
		HttpServletRequest request = ServletActionContext.getRequest();
		String lat = request.getParameter("lat");
		String lng = request.getParameter("lng");
		List<Point> listLocale = new ArrayList<Point>();
		
		String webSite = String.valueOf(request.getAttribute("webSite"));
		
	
		/*if( "yes".equals(webSite)){//如果是从其他网站过来的
			String websiteId = CookieUtil.getCookieValue(ServletActionContext.getRequest(), "c_websiteid");
			MWebsite websiteObj = commonManager.findEntityByPK(MWebsite.class, Long.parseLong(websiteId));
			
			List<Point> list = new ArrayList<Point>();
			
			String type = request.getParameter("type");
			if( type!=null && ("1".equals(type) || "4".equals(type))){
				type = "1";
			}else if(  type!=null && ("2".equals(type) || "5".equals(type))){
				type = "2";
			}else if(  type!=null && ("3".equals(type) || "6".equals(type))){
				type = "3";
			}
			
			if( CommUtils.isCorrectInt(type) && type.equals("1")){
				list = this.getPointsByWWW(websiteObj.getServiceForFCL());
			}else if( CommUtils.isCorrectInt(type) && type.equals("2")){
				list = this.getPointsByWWW(websiteObj.getServiceForLCL());
			}else if( CommUtils.isCorrectInt(type) && type.equals("3")){
				list = this.getPointsByWWW(websiteObj.getServiceForAIR());
			}
			
			if( lat!=null ){
				List<Point>list2 = pointManager.searchPointGEO(portType,lat,lng);
				listLocale = this.matchWWW(list, list2);
			}else{
				if( list!=null && list.size()>0 ){
					listLocale = matchName(list,keyword);
				}else{
					listLocale = pointManager.searchPoint(portType, keyword);
				}
			}
		}else{
			if( lat!=null ){
				listLocale = pointManager.searchPointGEO(portType,lat,lng);
			}else{
				listLocale = pointManager.searchPoint(portType, keyword);
			}
		}*/
		
		if( lat!=null ){
			listLocale = pointManager.searchPointGEO(portType,lat,lng);
		}else{
			listLocale = pointManager.searchPoint(portType, keyword);
		}
		
		String sign = "no";

		Document document = DocumentHelper.createDocument();
		document.setXMLEncoding("UTF-8");
		Element rootElement = document.addElement("root");
		Element countNode = rootElement.addElement("count");
		countNode.addAttribute("count", "1");
		if (listLocale != null && listLocale.size() > 0) {
			for (Point obj : listLocale) {
				Element searchObjNode = rootElement.addElement("searchObj");
				String value = obj.getFullname();
				String name = obj.getName();
				if (value.indexOf("'") == -1) {
					searchObjNode.addAttribute("value", value);
				} else {
					value = value.replaceAll("/'", "&acute;");
					searchObjNode.addAttribute("value", value);
				}
				searchObjNode.addAttribute("key", String.valueOf(obj.getId()));
				searchObjNode.addAttribute("type", String.valueOf(obj.getType()));
				searchObjNode.addAttribute("localName", name);
			}
			Element signNode = rootElement.addElement("signNode");
			signNode.addAttribute("sign", sign);
		}

		String outPutStr = document.asXML();
		try {
			Pattern pattern = Pattern.compile("\\([0-9]{4,10}\\)|\\*");
			Matcher m = pattern.matcher(outPutStr);
			outPutStr = m.replaceAll("");
		} catch (Exception e) {

		}
		outputData(outPutStr);
		return null;
	}
	
	public String getMaps() {
		// System.out.println("Maps Point ID: " + id);
		return "get";
	}

	public String adminSetMaps() {
		point = commonManager.findEntityByPK(Point.class, id);
		return "set";
	}
	
	public String adminSaveMaps() {
		try {
			String[] str = keyword.split(";");
			point = commonManager.findEntityByPK(Point.class, Long.valueOf(str[0]));
			point.setLatitude(Double.valueOf(str[1]));
			point.setLongitude(Double.valueOf(str[2]));
			point.setZoomLevel(Integer.valueOf(str[3]));
			commonManager.modifyEntity(point);
		} catch (NumberFormatException e) {
			e.printStackTrace();
		}
		return "save";
	}
	
	/**
	 * @param type: FCL/LCL时传值0查周边海港，AIR时传值1查周边空港，跟point类型无关
	 * @param first: 传"yes"为出发地，"no"或不传为目的地
	 * @return
	 */
	@Action("neighboringPorts")
	public String neighboringPorts() {
		if (detail != null && detail.equals("yes")) {
			detail = "yes";
		} else {
			detail = "no";
		}
		if (first != null && first.equals("yes")) {
			first = "yes";
		} else {
			first = "no";
		}
		if (pid != null && !pid.equals("0")) {
			point = commonManager.findEntityByPK(Point.class, Long.valueOf(pid));
			latlngs = pointManager.getNeighboringPorts(point, type);
			if (point.getZoomLevel() != null) {
				zoom = point.getZoomLevel();
			} else {
				zoom = 16;
			}
		}
		return "neighboringPorts";
	}
	
	public String batch() {
		latlngs = pointManager.getNoLatLngPoints();
		return "batch";
	}

	// 删除地点
	public void deletePoint() {
		HttpServletRequest request = ServletActionContext.getRequest();
		int result = 0;
		String pointStr = request.getParameter("pid");
		if (pointStr == null || pointStr == "") {
			pointStr = "0";
		}
		Long pointId = Long.parseLong(pointStr);
		point = commonManager.findEntityByPK(Point.class, pointId);
		if (pointManager.isPointCanDelete(point)) {
			commonManager.deleteEntity(point);
			result = 1;// 删除成功
		} else {
			result = 2;// 数据关联
		}
		outputData(result);
	}

	// 进入地名分组列表
	@SuppressWarnings("unchecked")
	public String toPointGroupList() {
		HttpServletRequest request = ServletActionContext.getRequest();
		List<QueryParam> queryParam = new ArrayList<QueryParam>();

		if (pointGroupName != null && !"".equals(pointGroupName)) {
			QueryParam param2 = new QueryParam();
			param2.setField("name");
			param2.setOp(OP.like);
			param2.setValue(new Object[] { "%" + pointGroupName + "%" });
			queryParam.add(param2);
		}

		if (pageSize == 0)
			pageSize = 15;
		if (pageNumber == 0)
			pageNumber = 1;
		pager = this.commonManager.findPageByCustomized(pageNumber, pageSize, PointGroup.class, queryParam, null);
		pointGroupList = pager.getCurrentPageElements();
		request.setAttribute("pageCount", pager.getLastPageNumber());
		return SUCCESS;
	}

	// 进入地名列表
	@SuppressWarnings("unchecked")
	public String toPointList() {
		HttpServletRequest request = ServletActionContext.getRequest();
		List<QueryParam> queryParam = new ArrayList<QueryParam>();
		QueryParam param = new QueryParam();
		param.setField("type");
		param.setOp(OP.equal);
		param.setValue(new Object[] { type });
		queryParam.add(param);

		QueryOrder order = new QueryOrder();
		order.setField("country.countryName");
		order.setAscOrder(true);

		QueryOrder order1 = new QueryOrder();
		order1.setField("fullnameNoSymbol");
		order1.setAscOrder(true);
		List<QueryOrder> queryOrder = new ArrayList<QueryOrder>();
		queryOrder.add(order);

		if (pointName != null && !"".equals(pointName)) {
			QueryParam param2 = new QueryParam();
			param2.setField("name");
			param2.setOp(OP.like);
			param2.setValue(new Object[] { "%" + pointName + "%" });
			queryParam.add(param2);
		}
		if (pointGroup != null && pointGroup.getId() != null && pointGroup.getId() != 0) {
			QueryParam param2 = new QueryParam();
			param2.setField(" pointGroupId=" + pointGroup.getId());
			param2.setOp(OP.sql);
			param2.setValue(new Object[] {});
			queryParam.add(param2);
		}
		if (countryName != null && !"".equals(countryName)) {
			QueryParam param2 = new QueryParam();
			param2.setField("country.countryName");
			param2.setOp(OP.like);
			param2.setValue(new Object[] { "%" + countryName + "%" });
			queryParam.add(param2);
		}
		if (basePort == 1 && type != 2) {
			QueryParam param2 = new QueryParam();
			param2.setField("basePort");
			param2.setOp(OP.equal);
			param2.setValue(new Object[] { basePort });
			queryParam.add(param2);
		}
		if (type == 1 && airCode != null && !"".equals(airCode)) {
			QueryParam param2 = new QueryParam();
			param2.setField("airCode");
			param2.setOp(OP.like);
			param2.setValue(new Object[] { "%" + airCode + "%" });
			queryParam.add(param2);
		}
		if(positionFlag==1){
			QueryParam param2 = new QueryParam();
			param2.setField(" (longitude is not null and latitude is not null and zoomLevel is not null)");
			param2.setOp(OP.sql);
			param2.setValue(new Object[] {});
			queryParam.add(param2);
		}else if(positionFlag==2){
			QueryParam param2 = new QueryParam();
			param2.setField(" (longitude is null or latitude is null or zoomLevel is null)");
			param2.setOp(OP.sql);
			param2.setValue(new Object[] {});
			queryParam.add(param2);
		}
		
		if (pageSize == 0)

			pageSize = 15;
		if (pageNumber == 0)
			pageNumber = 1;
		pager = this.commonManager.findPageByCustomized(pageNumber, pageSize, Point.class, queryParam, queryOrder);
		pointList = pager.getCurrentPageElements();
		request.setAttribute("pageCount", pager.getLastPageNumber());
		// 获取全部分组
		pointGroupList = this.commonManager.findByCustomized(PointGroup.class, null, null);
		return SUCCESS;
	}

	// 进入新增或修改页面
	public String toAddOrEditPoint() {
		List<QueryOrder> queryOrder = new ArrayList<QueryOrder>();
		QueryOrder order = new QueryOrder();
		order.setField("countryName");
		order.setAscOrder(true);
		queryOrder.add(order);

		countryList = commonManager.findByCustomized(Country.class, null, queryOrder);
		HttpServletRequest request = ServletActionContext.getRequest();
		String pointStr = request.getParameter("pid");
		if (pointStr == null || pointStr == "") {
			pointStr = "0";
			Long pointId = Long.parseLong(pointStr);
			point = new Point();
			point.setId(pointId);
		} else {
			Long pointId = Long.parseLong(pointStr);
			point = commonManager.findEntityByPK(Point.class, pointId);
		}
		pointGroupList = this.commonManager.findByCustomized(PointGroup.class, null, null);
		return SUCCESS;
	}

	// 保存或修改地名
	public void savePoint() {
		try {
			country = commonManager.findEntityByPK(Country.class, point.getCountry().getId());
			point.setCountry(country);
			int result = pointManager.savePoint(point);
			outputData(result);
		} catch (Exception e) {
			outputData(2);
		}
	}

	// 保存
	public void savePointGroup() {
		List<QueryParam> queryParam = new ArrayList<QueryParam>();
		QueryParam param = new QueryParam();
		param.setField("name");
		param.setOp(OP.equal);
		param.setValue(new Object[] { pointGroup.getName() });
		queryParam.add(param);
		pointGroupList = this.commonManager.findByCustomized(PointGroup.class, queryParam, null);
		if (pointGroupList == null || pointGroupList.size() == 0) {
			if (pointGroup.getId() == null || pointGroup.getId() == 0) {
				this.commonManager.saveEntity(pointGroup);
			} else {
				this.commonManager.modifyEntity(pointGroup);
			}
			outputData(0);
		} else {
			outputData(1);
		}
	}

	public void delPointGroup() {
		try {
			HttpServletRequest request = ServletActionContext.getRequest();
			String pgid = request.getParameter("pgid");
			if (pgid != null && !"".equals(pgid)) {
				pointGroup = this.commonManager.findEntityByPK(PointGroup.class, Long.parseLong(pgid));
				this.commonManager.deleteEntity(pointGroup);
				pointManager.updatePointGroup("(" + pgid + ")");
			} else {
				String delPointGroupId = request.getParameter("delPointGroupId");
				int index = delPointGroupId.lastIndexOf(",");
				delPointGroupId = delPointGroupId.substring(0, index);
				pointManager.updatePointGroup("(" + delPointGroupId + ")");
			}

			outputData(0);
		} catch (Exception e) {
			outputData(1);
		}
	}


	// 打开添加组页面
	public String toAddPointGroupName() {
		HttpServletRequest request = ServletActionContext.getRequest();
		String pgid = request.getParameter("pgid");
		String isAddPg=request.getParameter("isAddPg");
		if (pgid != null && !"".equals(pgid)) {
			pointGroup = this.commonManager.findEntityByPK(PointGroup.class, Long.parseLong(pgid));
		}
		request.setAttribute("isAddPg", isAddPg);
		return SUCCESS;
	}

	// 打开删除组页面
	public String toDelPointGroupName() {
		pointGroupList = this.commonManager.findByCustomized(PointGroup.class, null, null);
		return SUCCESS;
	}
	
	//在地点分组中添加地点
	public void addPointToGroup(){
		try {
			HttpServletRequest request = ServletActionContext.getRequest();
			String pid=request.getParameter("pid");
			String pointGroupId=request.getParameter("pointGroupId");
			PointGroup pointGroup=this.commonManager.findEntityByPK(PointGroup.class, Long.parseLong(pointGroupId));
			Point point=this.commonManager.findEntityByPK(Point.class, Long.parseLong(pid));
			point.setPointGroup(pointGroup);
			this.commonManager.modifyEntity(point);
			outputData(0);
		} catch (Exception e) {
			e.printStackTrace();
			outputData(1);
		}
	}
	
	//在地点分组中移除地点
	public void delPointFromGroup(){
		try {
			HttpServletRequest request = ServletActionContext.getRequest();
			String pid=request.getParameter("pid");
			Point point=this.commonManager.findEntityByPK(Point.class, Long.parseLong(pid));
			this.pointManager.updatePointGroup(Long.parseLong(pid));
			outputData(0+"|"+point.getPointGroup().getId());
		} catch (Exception e) {
			e.printStackTrace();
			outputData(1);
		}
	}
	
	//根据分组查该分组的地点列表
	public String getPointListByGroup() {
		HttpServletRequest request = ServletActionContext.getRequest();
		String pgid=request.getParameter("pgid");
		pointGroup=this.commonManager.findEntityByPK(PointGroup.class, Long.parseLong(pgid));
		List<QueryParam> queryParam = new ArrayList<QueryParam>();
		if(pgid!=null && !"".equals(pgid)){
			QueryParam param2 = new QueryParam();
			param2.setField(" pointGroupId=" + pgid);
			param2.setOp(OP.sql);
			param2.setValue(new Object[] {});
			queryParam.add(param2);
		}

		QueryOrder order = new QueryOrder();
		order.setField("country.countryName");
		order.setAscOrder(true);

		QueryOrder order1 = new QueryOrder();
		order1.setField("fullnameNoSymbol");
		order1.setAscOrder(true);
		List<QueryOrder> queryOrder = new ArrayList<QueryOrder>();
		queryOrder.add(order);
		
		pointList =this.commonManager.findByCustomized(Point.class, queryParam, queryOrder);
		
		return SUCCESS;
	}

	// 输出数据
	private void outputData(Object obj) {
		HttpServletResponse response = ServletActionContext.getResponse();
		response.setCharacterEncoding("UTF-8");
		response.setContentType("text/html;charset=utf-8");
		try {
			response.getWriter().print(obj);
		} catch (IOException e) {
			e.printStackTrace();
		}
	}

	public CommonManager getCommonManager() {
		return commonManager;
	}

	public void setCommonManager(CommonManager commonManager) {
		this.commonManager = commonManager;
	}

	public Country getCountry() {
		return country;
	}

	public void setCountry(Country country) {
		this.country = country;
	}

	public List<Country> getCountryList() {
		return countryList;
	}

	public void setCountryList(List<Country> countryList) {
		this.countryList = countryList;
	}

	public String getKeyword() {
		return keyword;
	}

	public void setKeyword(String keyword) {
		this.keyword = keyword;
	}

	public int getModuleFlag() {
		return moduleFlag;
	}

	public void setModuleFlag(int moduleFlag) {
		this.moduleFlag = moduleFlag;
	}

	public int getPageNumber() {
		return pageNumber;
	}

	public void setPageNumber(int pageNumber) {
		this.pageNumber = pageNumber;
	}

	@SuppressWarnings("rawtypes")
	public Page getPager() {
		return pager;
	}

	public void setPager(@SuppressWarnings("rawtypes") Page pager) {
		this.pager = pager;
	}

	public int getPageSize() {
		return pageSize;
	}

	public void setPageSize(int pageSize) {
		this.pageSize = pageSize;
	}

	public Point getPoint() {
		return point;
	}

	public void setPoint(Point point) {
		this.point = point;
	}

	public List<Point> getPointList() {
		return pointList;
	}

	public void setPointList(List<Point> pointList) {
		this.pointList = pointList;
	}

	public IPointManager getPointManager() {
		return pointManager;
	}

	public void setPointManager(IPointManager pointManager) {
		this.pointManager = pointManager;
	}

	public int getPortType() {
		return portType;
	}

	public void setPortType(int portType) {
		this.portType = portType;
	}

	public String getPointName() {
		return pointName;
	}

	public void setPointName(String pointName) {
		this.pointName = pointName;
	}

	public int getType() {
		return type;
	}

	public void setType(int type) {
		this.type = type;
	}

	public String getPointGroupName() {
		return pointGroupName;
	}

	public void setPointGroupName(String pointGroupName) {
		this.pointGroupName = pointGroupName;
	}

	public String getCommonGroupName() {
		return commonGroupName;
	}

	public void setCommonGroupName(String commonGroupName) {
		this.commonGroupName = commonGroupName;
	}

	public String getCountryName() {
		return countryName;
	}

	public void setCountryName(String countryName) {
		this.countryName = countryName;
	}

	public PointGroup getPointGroup() {
		return pointGroup;
	}

	public void setPointGroup(PointGroup pointGroup) {
		this.pointGroup = pointGroup;
	}

	public List<PointGroup> getPointGroupList() {
		return pointGroupList;
	}

	public void setPointGroupList(List<PointGroup> pointGroupList) {
		this.pointGroupList = pointGroupList;
	}

	public int getBasePort() {
		return basePort;
	}

	public void setBasePort(int basePort) {
		this.basePort = basePort;
	}

	public String getAirCode() {
		return airCode;
	}

	public void setAirCode(String airCode) {
		this.airCode = airCode;
	}

	public long getId() {
		return id;
	}

	public void setId(long id) {
		this.id = id;
	}

	public String getPid() {
		return pid;
	}

	public void setPid(String pid) {
		this.pid = pid;
	}

	public String getLatlngs() {
		return latlngs;
	}

	public void setLatlngs(String latlngs) {
		this.latlngs = latlngs;
	}

	public int getPositionFlag() {
		return positionFlag;
	}

	public void setPositionFlag(int positionFlag) {
		this.positionFlag = positionFlag;
	}

	public String getDetail() {
		return detail;
	}

	public void setDetail(String detail) {
		this.detail = detail;
	}

	public int getZoom() {
		return zoom;
	}

	public void setZoom(int zoom) {
		this.zoom = zoom;
	}

	public String getFirst() {
		return first;
	}

	public void setFirst(String first) {
		this.first = first;
	}

}
